<template>
    <div class="nav">
        <div class="wrapper">
            <div class="block">
                <video id="video" autoplay playsinline></video>
                <!-- 添加聚焦提示框容器，初始时隐藏 -->
                <div ref="focusIndicator" class="focus-indicator" style="display: none;"></div>
            </div>
            <!-- 移动按钮到 .block 下方，并添加新的 div 作为容器 -->
            <div class="button-container">
                <span id="close" @click.stop="goBack">取消</span>
                <span id="capture" @click.stop="onCaptureClick">拍摄</span>
                <span>反转</span>
            </div>
        </div>
        <EditAvatar :show="show" :imgUrl="imgUrl" @closePopup="onClosePopup" />
    </div>
</template>

<script lang="ts" setup>
import { onMounted, onUnmounted, ref, watch, type Ref } from 'vue';
import { useRouter } from 'vue-router'
import EditAvatar from '../components/EditAvatar.vue';
const router = useRouter()

interface MediaTrackConstraints {
    advanced: any;
}

const goBack = () => {
    router.go(-1)
}

const show: Ref<boolean> = ref(false)

const onClosePopup = () => {
    show.value = false // 收到子组件的closePopup事件后，关闭popup
}

// 声明一个全局变量来存储获取到的媒体流
let mediaStream: MediaStream | null = null;

const focusIndicator = ref<HTMLElement | null>(null);

// 图片文件
const imgUrl: Ref<string> = ref('');

onMounted(() => {
    const constraints = {
        audio: false, // 音频请求
        video: {
            width: { ideal: window.screen.height * (9 / 16) },
            height: { ideal: window.screen.height },
            facingMode: "user", // 用户设备前置摄像头
            autoFocus: true, // 自动对焦
            frameRate: { ideal: 144 }, // 理想帧率
        },
    };

    navigator.mediaDevices
        .getUserMedia(constraints)
        .then((stream) => {
            console.log('MediaStream Success');
            mediaStream = stream; // 将获取到的媒体流赋值给全局变量 mediaStream
            const video = document.getElementById("video") as HTMLVideoElement;
            video.srcObject = mediaStream;
            video.onloadedmetadata = function () {
                video.play();
            };
            const settings = mediaStream.getVideoTracks()[0].getSettings();
            // MediaStreamTrack 实际设置（即当前生效的约束）的对象。
            // console.log('settings', settings);

            const capabilities = mediaStream.getVideoTracks()[0].getCapabilities();
            // MediaStreamTrack 所连接设备或源支持的各种能力（即可能的约束范围）的对象。
            // console.log('capabilities', capabilities);

        })
        .catch((err) => {
            console.log(err.name + ": " + err.message);
        }); // 总是在最后检查错误

    // 在视频元素上添加点击事件监听器
    const videoElement = document.querySelector('#video') as Element;
    videoElement.addEventListener('click', onVideoClick);
})

onUnmounted(() => {
    // 关闭MediaStream
    function stopMediaStream() {
        if (mediaStream) {
            mediaStream.getTracks().forEach(track => track.stop());
            mediaStream = null;
            console.log('MediaStream Close');
        }
    }
    stopMediaStream(); // 清除媒体流
})

const takeSnapshot = async (): Promise<string> => {
    const video: HTMLVideoElement = document.getElementById("video") as HTMLVideoElement;
    if (!video) return '';

    // 创建一个与视频同尺寸的canvas
    const canvas: HTMLCanvasElement = document.createElement('canvas');
    canvas.width = video.videoWidth;
    canvas.height = video.videoHeight;

    // 使用canvas绘制视频当前帧
    const ctx = canvas.getContext('2d');
    if (!ctx) {
        console.error('Canvas context not supported.');
        return '';
    }
    ctx.drawImage(video, 0, 0, canvas.width, canvas.height);

    // 将canvas内容转换为data URL（base64编码）
    const dataUrl = canvas.toDataURL('image/jpeg', 1.0); // 可选第二个参数设置质量，范围0.0-1.0
    
    return dataUrl;
};

// 添加一个新的函数用于在下一帧渲染时调用takeSnapshot
function scheduleSnapshot() {
    requestAnimationFrame(async () => {
        const dataUrl = await takeSnapshot();
        // 在这里处理获取到的数据URL，如保存至服务器或显示预览等
        // console.log('Snapshot taken:', dataUrl);
        imgUrl.value = dataUrl;

        // 显示预览
        show.value = true
    });
}

// 更新“拍摄”按钮的点击事件处理函数
function onCaptureClick() {

    // 在下一帧渲染时调用takeSnapshot()
    scheduleSnapshot();
}


function onVideoClick(event: any) {
    //MediaStreamTrack.applyConstraints(): 
    // 官方文档详细介绍了 MediaStreamTrack.applyConstraints() 方法，包括如何使用它来调整视频轨道的约束
    // 聚焦
    // 注意：此功能仅适用于支持 MediaStreamTrack.applyConstraints() 的浏览器和设备
    if (mediaStream) {
        const track = mediaStream.getVideoTracks()[0];
        const rect = (event.target as Element).getBoundingClientRect();
        const x = ((event.clientX - rect.left) / event.target.clientWidth) * 2 - 1;
        const y = ((event.clientY - rect.top) / event.target.clientHeight) * 2 - 1;

        const constraints: MediaTrackConstraints = {
            advanced: [
                {
                    focusMode: 'manual', // 或 'auto'，根据实际需求
                    focusPoint: {
                        x: x,
                        y: y,
                    },
                },
            ],
        };

        track.applyConstraints(constraints)
            .then(() => console.log('Focus point applied'))
            .catch(err => {
                if (err instanceof OverconstrainedError) {
                    console.warn('This browser or device does not support manual focus adjustments. Focus operation skipped.');
                } else {
                    console.error('An error occurred while applying focus point:', err);
                }
            });
    }

    // 用户快速“聚焦”导致区域显示异常（未2秒消失），卡顿问题

    // 获取视频元素的边界信息
    const videoElement = document.getElementById("video") as HTMLElement;
    const videoRect = videoElement.getBoundingClientRect();

    // 显示并定位聚焦提示框
    const indicator = focusIndicator.value as HTMLElement;
    if (indicator) {
        indicator.style.display = 'block';
        indicator.style.left = `${event.clientX - videoRect.left - 24}px`;
        indicator.style.top = `${event.clientY - videoRect.top - 24}px`;

        // 延迟一段时间后隐藏提示框（例如：1秒后）
        setTimeout(() => {
            indicator.style.display = 'none';
        }, 2000);
    }
}

</script>

<style lang="scss" scoped>
* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
    /* 确保边距和填充不会影响元素的实际尺寸 */
}

.nav {
    width: 100vw;
    height: 100vh;
    overflow: hidden;
    background-color: black;
    color: white;
    /* 防止内容溢出导航区域 */
}

.wrapper {
    display: flex;
    align-items: center;
    justify-content: center;
    height: 100%;
}

.block {
    margin-top: -20px;
    position: relative;
    width: 100%;
    height: 0;
    padding-bottom: 140%;
    /* 保持视频的宽高比为9:16 */
    overflow: hidden;

    &>video {
        position: absolute;
        top: 0;
        left: 0;
        width: 100%;
        height: 100%;
        object-fit: cover;
    }
}

.button-container {
    font-size: 18px;
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 70px;
    /* 添加适当的间距 */
    position: absolute;
    bottom: 20px;
    /* 距离底部的距离，可根据需要调整 */
    left: 0;
    right: 0;
    z-index: 1;
    /* 确保按钮在视频之上 */
}

.focus-indicator {
    position: absolute;
    width: 50px;
    height: 50px;
    border: 2px solid #ffffff;
    border-radius: 50%;
    pointer-events: none;
    /* 防止遮挡视频点击事件 */
}
</style>